47장. ECS Service와 ALB 연결하기
이 장에서 말하고자 하는 것
이제 우리는
- ECS의 구조 (Cluster / Task / Service)
- Task Definition 으로 컨테이너 정의
- Fargate를 쓸지 EC2를 쓸지
까지 다뤘다.
그런데 띄운 컨테이너에 트래픽이 들어오려면 ALB와 묶어야 한다.
이 장은 그 묶음을 본다.
1. 큰 그림
[ALB]
└─ Target Group (IP 타입)
↑ 자동 등록
[ECS Service]
├─ Task 1 (10.0.1.10)
├─ Task 2 (10.0.2.11)
└─ Task 3 (...)
핵심은
ECS Service가 새 Task를 띄울 때마다
그 Task의 IP를 자동으로 Target Group에 등록한다
는 점이다. 사람이 ALB에 IP를 박지 않는다.
2. Service의 loadBalancers 설정
ECS Service에 ALB Target Group을 묶는다.
Service "orders"
↳ TG ARN: tg-orders
↳ Container name: app
↳ Container port: 8080
ECS는 이걸 보고
- Task가 뜨면 → TG에 IP 등록
- Task가 죽으면 → TG에서 제거
3. Health Check 흐름
1. Service가 Task 띄움
2. 컨테이너 시작
3. ALB가 /health 요청 → 200
4. 연속 2번 성공 → Healthy
5. 트래픽 들어옴
6. 연속 2번 실패 → Unhealthy → TG에서 빠짐
7. Service가 새 Task 띄움
Service가 원하는 desiredCount를 유지하면서
죽은 Task는 자동 교체한다
4. Health Check Grace Period
Task가 막 떴는데 ALB가 곧장 체크하면
애플리케이션이 아직 부팅 중일 수 있다.
healthCheckGracePeriodSeconds: 60
이 시간 동안은 헬스 체크 실패를 무시한다.
부팅 느린 애플리케이션은 이 값을 충분히 둔다
안 그러면 ECS가 끝없이 Task를 죽이고 만들기를 반복한다
5. 우리 서비스에서
[ALB]
├─ TG-orders → ECS Service "orders" (2 task)
├─ TG-users → ECS Service "users" (2 task)
├─ TG-payments → ECS Service "payments" (2 task)
한 TG = 한 ECS Service = 한 마이크로서비스
6. 직접 확인해보기 — CLI
Service 만들기 (TG 연결)
aws ecs create-service \
--cluster my-cluster \
--service-name orders \
--task-definition orders:1 \
--desired-count 2 \
--launch-type FARGATE \
--load-balancers "targetGroupArn=<tg-arn>,containerName=app,containerPort=8080" \
--network-configuration "awsvpcConfiguration={subnets=[subnet-x,subnet-y],securityGroups=[sg-x]}" \
--health-check-grace-period-seconds 60
TG에 자동 등록된 Task 보기
aws elbv2 describe-target-health \
--target-group-arn <tg-arn>
응답의 Id 가 Task의 ENI IP다.
7. 코드로는 이렇게 생겼다 — Terraform
resource "aws_ecs_service" "orders" {
name = "orders"
cluster = aws_ecs_cluster.main.id
task_definition = aws_ecs_task_definition.orders.arn
desired_count = 2
launch_type = "FARGATE"
network_configuration {
subnets = [aws_subnet.private_a.id, aws_subnet.private_b.id]
security_groups = [aws_security_group.task.id]
}
load_balancer {
target_group_arn = aws_lb_target_group.orders.arn
container_name = "app"
container_port = 8080
}
health_check_grace_period_seconds = 60
deployment_circuit_breaker {
enable = true
rollback = true
}
}
deployment_circuit_breaker 는 배포가 실패하면
자동으로 이전 버전으로 돌아간다. 운영에 거의 항상 켠다.
8. 이렇게 쓰면 망한다 — 안티패턴
안티패턴 1. Service에 TG 없이 띄우고 외부에 직접 노출한다
Task의 IP는 자주 바뀐다. 도메인으로 가리킬 수 없다.
ECS Task는 항상 ALB / NLB의 TG 뒤에
안티패턴 2. Grace Period가 0이다
부팅 느린 앱이 끝없이 죽고 뜬다.
60~120초로 시작해서 줄여본다
안티패턴 3. 한 TG에 여러 Service를 묶는다
스케일링 · 배포 · 헬스 체크가 다 섞인다.
안티패턴 4. Circuit Breaker를 안 켠다
배포 실패해도 새 Task가 계속 뜨려다 죽는 무한 루프.
9. 한 줄로 정리
ECS Service는 Task를 ALB Target Group에 자동 등록하며,
헬스 체크 결과로 트래픽과 자가 치유를 함께 다룬다
10. 이 장의 핵심 정리
- ECS Service의 load_balancer 설정이 ALB TG와 묶는다.
- Task가 뜨면 IP가 자동 등록, 죽으면 제거된다.
- Grace Period로 부팅 중 헬스 체크를 무시할 수 있다.
- 한 Service = 한 TG = 한 마이크로서비스가 표준이다.
- deployment_circuit_breaker + rollback은 배포 안전망이다.